let a: string = 'Hello World';
console.log(a);

let decLiteral: number = 6;
let hexLiteral: number = 0xf00d;
let binaryLiteral: number = 0b1010;
let octalLiteral: number = 0o744;

console.log(decLiteral);
console.log(hexLiteral);
console.log(binaryLiteral);
console.log(octalLiteral);

let name: string = "bob";
console.log(name);
name = "smith";
console.log(name);

let namev: string = 'smith';
console.log(name == namev)

let name2: string = `Gene`;
let age: number = 37;
let sentence: string = `Hello, my name is ${ name }.I'll be ${ age + 1 } years old next month.`;

/*你还可以使用模版字符串，它可以定义多行文本和内嵌表达式。 这种字符串是被反引号包围（ `），并且以${ expr }这种形式嵌入表达式*/
console.log(sentence);

let sentence1: string = "Hello, my name is " + name + ".\n\n" +
    "I'll be " + (age + 1) + " years old next month.";

console.log(sentence1);

// 数组
/*TypeScript像JavaScript一样可以操作数组元素。 有两种方式可以定义数组。 第一种，可以在元素类型后面接上 []，表示由此类型元素组成的一个数组：*/
let list: number[] = [1, 2, 3];
console.log(list)

let list1: Array<number> = [1, 2, 3];
console.log(list1)

// 元组 Tuple
// 元组类型允许表示一个已知元素数量和类型的数组，各元素的类型不必相同。 比如，你可以定义一对值分别为 string和number类型的元组。
// Declare a tuple type
let x1: [string, number];
// Initialize it
x1 = ['hello', 10]; // OK
console.log(x1[0])
console.log(x1[1])

/*枚举 默认情况下，从0开始为元素编号。 你也可以手动的指定成员的数值。 例如，我们将上面的例子改成从 1开始编号：*/
export enum Color {Red = 'red', Green = 'green', Blue = 'blue'}

let c: Color = Color.Green;
console.log(c)

// Any
// 有时候，我们会想要为那些在编程阶段还不清楚类型的变量指定一个类型。 这些值可能来自于动态的内容，比如来自用户输入或第三方代码库。
// 这种情况下，我们不希望类型检查器对这些值进行检查而是直接让它们通过编译阶段的检查。 那么我们可以使用 any类型来标记这些变量：

let notSure: any = 4;
notSure = "maybe a string instead";
notSure = false; // okay, definitely a boolean

let list3: any[] = [1, true, "free"];
console.log(list3)
list3[1] = 100;

let someValue: any = "this is a string";

let strLength: number = (<string>someValue).length;
console.log(strLength);


let someValue1: any = "this is a string";
let strLength1: number = (someValue as string).length;
let strLength2: number = someValue.length;

console.log(strLength1)
console.log(strLength2)

export class Product {
    i?: string;

    constructor(public ix?: string) {

    }

    public test(): void {
        console.log('xxx');
        console.log(this.ix);
    }
}

let product: any = new Product('x');
let product1: Product = product;
product1.test();

// 它们与let声明相似，但是就像它的名字所表达的，它们被赋值后不能再改变。 换句话说，它们拥有与 let相同的作用域规则，但是不能对它们重新赋值。
const numLivesForCat = 9;
const kitty = {
    name: "Aurora",
    numLives: numLivesForCat,
}

// Error
// kitty = {
//     name: "Danielle",
//     numLives: numLivesForCat
// };

// all "okay"
kitty.name = "Rory";
kitty.name = "Kitty";
kitty.name = "Cat";
kitty.numLives--;

// 除非你使用特殊的方法去避免，实际上const变量的内部状态是可修改的。 幸运的是，TypeScript允许你将对象的成员设置成只读的。 接口一章有详细说明。